﻿using System;
using System.Collections.ObjectModel;
using System.Xml.Serialization;
using EpiNEXT.Core.Fields.Properties;

namespace EpiNEXT.Core.Fields
{
    [Serializable()]
    public abstract class Field : ObservableObject, IField
    {
        #region Members
        private string _fieldType = String.Empty;
        private bool _isEnabled = true;
        private bool _isCurrentlyEnabled = true;
        private string _promptFontFamily = "Segoe UI";
        private string _inputFontFamily = "Segoe UI";
        private double _inputHeight = Double.NaN;
        private double _inputWidth = Double.NaN;
        private double _inputLeft = Double.NaN;
        private double _inputTop = Double.NaN;
        private double _promptWidth = Double.NaN;
        private double _promptHeight = Double.NaN;
        #endregion // Members

        #region Properties
        [XmlElement("Id")]
        public Guid FieldId { get; set; }

        [XmlElement("PageId")]
        public Guid PageId { get; set; }

        [XmlElement]
        public bool IsEnabled
        {
            get
            {
                return this._isEnabled;
            }
            set
            {
                if (IsEnabled != value)
                {
                    this._isEnabled = value;
                    RaisePropertyChanged("IsEnabled");
                }
            }
        }

        [XmlIgnore]
        public bool IsCurrentlyEnabled
        {
            get
            {
                return this._isCurrentlyEnabled;
            }
            set
            {
                if (IsCurrentlyEnabled != value)
                {
                    this._isCurrentlyEnabled = value;
                    RaisePropertyChanged("IsCurrentlyEnabled");
                }
            }
        }

        [XmlElement]
        public bool IsHighlighted { get; set; }

        [XmlElement]
        public string Visibility { get; set; }

        [XmlElement]
        public string Name { get; set; }

        [XmlElement]
        public string Alias { get; set; }

        [XmlIgnore]
        public DataEntryInstrument Form { get; set; }

        [XmlIgnore]
        public Page Page { get; set; }

        [XmlElement]
        public bool IsTabStop { get; set; }

        [XmlElement]
        public int TabIndex { get; set; }

        [XmlElement]
        public string PromptText { get; set; }

        [XmlElement("InputBorderThickness", typeof(Thickness))]
        public Thickness InputBorderThickness { get; set; }

        [XmlIgnore]
        public virtual string DataType
        {
            get
            {
                return String.Empty;
            }
        }

        [XmlElement("PromptFontFamily")]
        public string PromptFontFamily
        {
            get
            {
                return this._promptFontFamily;
            }
            set
            {
                if (this.PromptFontFamily != value)
                {
                    this._promptFontFamily = value;
                    RaisePropertyChanged("PromptFontFamily");
                }
            }
        }

        [XmlElement("InputFontFamily")]
        public string InputFontFamily
        {
            get
            {
                return this._inputFontFamily;
            }
            set
            {
                if (this.InputFontFamily != value)
                {
                    this._inputFontFamily = value;
                    RaisePropertyChanged("InputFontFamily");
                }
            }
        }

        [XmlElement]
        public double? PromptFontSize { get; set; }

        [XmlElement]
        public string PromptFontWeight { get; set; }

        /// <summary>
        /// Gets/sets a prompt text translations for the form
        /// </summary>
        [XmlArray("PromptTranslations")]
        [XmlArrayItem("PromptTranslation", typeof(FieldTextPropertyTranslation))]
        public ObservableCollection<FieldTextPropertyTranslation> PromptTranslations { get; set; }

        [XmlArray("ColumnNameTranslations")]
        [XmlArrayItem("ColumnNameTranslation", typeof(FieldTextPropertyTranslation))]
        public ObservableCollection<FieldTextPropertyTranslation> ColumnNameTranslations { get; set; }

        [XmlElement]
        public double ControlBorderCornerRadius { get; set; }

        [XmlElement("PromptForegroundColor", typeof(Color))]
        public Color PromptForegroundColor { get; set; }

        [XmlElement]
        public double InputWidth
        {
            get { return this._inputWidth; }
            set
            {
                if (InputWidth != value)
                {
                    this._inputWidth = value;
                    RaisePropertyChanged("InputWidth");
                }
            }
        }

        [XmlElement]
        public double InputHeight
        {
            get { return this._inputHeight; }
            set
            {
                if (InputHeight != value)
                {
                    this._inputHeight = value;
                    RaisePropertyChanged("InputHeight");
                }
            }
        }

        [XmlElement]
        public double InputLeft
        {
            get { return this._inputLeft; }
            set
            {
                if (InputLeft != value)
                {
                    this._inputLeft = value;
                    RaisePropertyChanged("InputLeft");
                }
            }
        }

        [XmlElement]
        public double InputTop
        {
            get { return this._inputTop; }
            set
            {
                if (InputTop != value)
                {
                    this._inputTop = value;
                    RaisePropertyChanged("InputTop");
                }
            }
        }

        [XmlElement]
        public double InputFontSize { get; set; }

        [XmlElement]
        public string InputFontWeight { get; set; }

        [XmlElement]
        public double PromptLeft { get; set; }

        [XmlElement]
        public double PromptTop { get; set; }

        [XmlElement]
        public double PromptWidth
        {
            get { return this._promptWidth; }
            set
            {
                if (PromptWidth != value)
                {
                    this._promptWidth = value;
                    RaisePropertyChanged("PromptWidth");
                }
            }
        }

        [XmlElement]
        public double PromptHeight
        {
            get { return this._promptHeight; }
            set
            {
                if (PromptHeight != value)
                {
                    this._promptHeight = value;
                    RaisePropertyChanged("PromptHeight");
                }
            }
        }

        [XmlIgnore]
        public string FieldType
        {
            get
            {
                return this._fieldType;
            }
            private set
            {
                this._fieldType = value;
                RaisePropertyChanged("FieldType");
            }
        }
        #endregion // Properties

        #region Constructors
        public Field()
            : base()
        {
            FieldId = Guid.NewGuid();
            FieldType = this.GetType().ToString().Replace("EpiNEXT.Core.Fields.", String.Empty);
            PromptHeight = Double.NaN;
            PromptWidth = Double.NaN;
            PromptForegroundColor = new Color(255, 51, 51, 51);
            InputBorderThickness = new Thickness(1, 1, 1, 1);
        }
        #endregion // Constructors
    }
}
